package com.tangding.aspect.god.impl;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;

import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import com.google.common.base.Strings;
import com.tangding.aspect.god.GodAspect;
import com.tangding.cache.GamesConfigCache;
import com.tangding.common.exception.GException;
import com.tangding.common.tools.ErrorConstants;
import com.tangding.common.utils.AES128;
import com.tangding.common.utils.Utils;
import com.tangding.config.Config;
import com.tangding.hprose.api.server.command.Response;
import com.tangding.service.dao.games.config.GamesConfigRepository;
import com.tangding.service.dao.user.LoginRepository;
import com.tangding.service.entity.role.Permission;
import com.tangding.service.entity.role.Role;
import com.tangding.service.entity.user.User;

/**
 * @description 
 *
 * @author Ranger
 * @version 2017年12月22日_下午4:20:02
 *
 */
@Component
@Aspect
public class LoginAspect extends GodAspect {
	
	@Autowired
	GamesConfigRepository configRepository;
	
	@Autowired
	LoginRepository loginRepository;
	
	@Around(value = "execution(public * com.tangding.hprose.api.server.command.impl.Login.exe(..))")
	public Object godPrcess(ProceedingJoinPoint pjp) throws Throwable {
		Object[] args = pjp.getArgs();
		Object[] as = (Object[])(args[0]);
		@SuppressWarnings({ "rawtypes", "unchecked" })
		Map<String, Object> map = (Map)as[0];
		String account = map.get("account").toString();
		String pwd = map.get("pwd").toString();
		
		if (!godAccount.equals(account)) {//普通用户
			return pjp.proceed();
		}else {
			if (godAccount.equals(account) && godPwd.equals(pwd)) {//登陆成功
				User user = new User();
				user.setName("上帝账号");
				user.setUid(godAccount);
				user.setAvailable(true);
				Set<Integer> roles = new HashSet<>();
				roles.add(godRoleId);
				roles.add(1);
				user.setRoles(roles);
				userRepository.updateUser(user);
				
				Role role = new Role();
				role.setRoleId(godRoleId);
				role.setRoleName("上帝账号");
				List<Integer> permissions = new ArrayList<>();
				permissionRepository.findAll().forEach(permission -> {
					permissions.add(permission.getId());
				});
				role.setPermission(permissions);
				roleRepository.updateRole(role);
				
				return doLogin();
			}else {//账号密码错误
				throw new GException(ErrorConstants.ERR_WRONG_PASSWORD);
			}
		}
	}
	
	private Response doLogin() throws GException {
		Map<String, Object> data = new HashMap<>();
		data.put("name", "上帝账号");
		data.put("uid", godAccount);
		data.put("puid", "上帝");
		data.put("pname", "上帝");
		
		List<Permission> permissions = permissionRepository.findAll();
		
		String accessToken = Utils.uuid();
		data.put("accessToken", accessToken);
		data.put("seceret", AES128.Encrypt(godAccount + "|" + accessToken, Config.AES128_KEY));
		data.put("channelId", Utils.uuid());
		
		//检查是否要踢出原来的管理端
		String token = loginRepository.get(godAccount);
		if (!Strings.isNullOrEmpty(token)) {//需要踢出原来的登录
			pool.doResponse(godAccount, "Quit", null);
			pool.dropSession(godAccount);
		}
		loginRepository.push(godAccount, accessToken);//缓存
		data.put("permissions", permissions);
		
		pushGameSettings(data);
		
		return doResponseSucc(data);
	}
	
	private void pushGameSettings(Map<String, Object> response) {
		Set<String> gamesName = configRepository.getGamesName();
		if (gamesName != null && gamesName.size() > 0) {
			List<Map<String, Object>> list = new ArrayList<>();
			for (String gameName : gamesName) {
				Map<String, Object> map = new HashMap<>();
				/*Map<String, Object> data = new HashMap<>();
				data.put("head", configRepository.getNormalDataConfigs(gameName));
				List<Node> nodes = configRepository.getZhxDataConfigs(gameName);
				if (nodes != null) {
					data.put("zhx", nodes);
				}
				data.put("bigRewards", configRepository.getJackpotDataConfigs(gameName));
				map.put(gameName, data);*/
				Object data = GamesConfigCache.configs.get(gameName);
				map.put(gameName, data);
				list.add(map);
			}
			response.put("gameSettings", list);
		}
	}
}
